import { Cards, Card, Steps, Tabs } from 'nextra/components'
import BadgeGroup, { UniverTypes } from '@/components/BadgeGroup'

# Quickstart

<BadgeGroup values={[UniverTypes.SHEET, UniverTypes.DOC]} value={UniverTypes.SHEET} />

If you want to get started with Univer as quickly as possible, you've come to the right place! This page will guide you through building a working Univer app in just a few minutes.

## Play Online

You can play with Univer online without installing anything. Just click the link below and start using Univer right away.

<Cards>
  <Card
    icon="📊"
    title={<span className="">Univer Sheet</span>}
    href="https://stackblitz.com/~/github.com/awesome-univer/sheets-vite-demo"
  />
</Cards>

## Starter Kit

If you prefer to start with a local development environment, you can use the following starter kits to create a new Univer app in just a few seconds.

<Tabs items={['pnpm', 'npm']}>
  <Tabs.Tab label="pnpm">
    ```shell
    pnpm dlx degit dream-num/univer-sheet-start-kit [your-app-name]
    ```
  </Tabs.Tab>
  <Tabs.Tab label="npm">
    ```shell
    npx degit dream-num/univer-sheet-start-kit [your-app-name]
    ```
  </Tabs.Tab>
</Tabs>

Great job on your first steps with Univer! You've successfully created your first project and gotten a taste of what Univer can do.

## Integrated Server Template

Of course, you may want more than just the basics. If you're looking to add features like printing, importing/exporting, and collaborative editing, you'll need additional configuration and server support. But don't worry, Univer has you covered! Follow the steps below to quickly experience these advanced features.

<Steps>
  ### Install and Run the Server

  ```shell
  sh -c "$(curl -fsSL https://release-univer.oss-cn-shenzhen.aliyuncs.com/release-demo/install.sh)"
  ```

  ### Install and Run the Frontend

  <Tabs items={['pnpm', 'npm', 'Without package manager']}>
    <Tabs.Tab label="pnpm">
      ```shell
      pnpm dlx degit dream-num/univer-pro-sheet-start-kit [your-app-name]
      cd [your-app-name] && pnpm install # pnpm version >= 8
      pnpm dev
      ```

      🎉 Congratulations! You've successfully created another Univer project with a server. You can now visit [http://localhost:5173/](http://localhost:5173/) to experience these advanced features.

      You can also find the source code for this template at [dream-num/univer-pro-sheet-start-kit](https://github.com/dream-num/univer-pro-sheet-start-kit).
    </Tabs.Tab>

    <Tabs.Tab label="npm">
      ```shell
      npx degit dream-num/univer-pro-sheet-start-kit [your-app-name]
      cd [your-app-name] && npm install # npm version >= 7
      npm run dev
      ```

      🎉 Congratulations! You've successfully created another Univer project with a server. You can now visit [http://localhost:5173/](http://localhost:5173/) to experience these advanced features.

      You can also find the source code for this template at [dream-num/univer-pro-sheet-start-kit](https://github.com/dream-num/univer-pro-sheet-start-kit).
    </Tabs.Tab>
    <Tabs.Tab label="Without package manager">
      If you want to run Univer directly in the browser without any frontend build tools, you can copy and save the following code to an HTML file, then double-click to open the file in the browser to experience features like printing, collaborative editing, importing/exporting, etc.

      ```html
      <!DOCTYPE html>
      <html lang="en">
      <head>
        <meta charset="UTF-8">
        <meta name="viewport" content="width=device-width, initial-scale=1.0">
        <title>
          Univer UMD With Collaboration, Live Share, Print, Exchange
        </title>
        <script src="https://unpkg.com/@univerjs/umd/lib/univer.full.umd.js"></script>
        <script src="https://unpkg.com/@univerjs/umd/lib/locale/en-US.js"></script>
        <link rel="stylesheet" href="https://unpkg.com/@univerjs/umd/lib/univer.css">

        <script src="https://unpkg.com/lodash/lodash.js"></script>
        <script> window.lodash = _ </script>

        <script src="https://unpkg.com/@univerjs-pro/collaboration/lib/umd/index.js"></script>
        <script src="https://unpkg.com/@univerjs-pro/collaboration-client/lib/umd/index.js"></script>
        <link rel="stylesheet" href="https://unpkg.com/@univerjs-pro/collaboration-client/lib/index.css">

        <script src="https://unpkg.com/@univerjs-pro/live-share/lib/umd/index.js"></script>
        <link rel="stylesheet" href="https://unpkg.com/@univerjs-pro/live-share/lib/index.css">

        <script src="https://unpkg.com/@univerjs-pro/print/lib/umd/index.js"></script>
        <script src="https://unpkg.com/@univerjs-pro/sheets-print/lib/umd/index.js"></script>
        <link rel="stylesheet" href="https://unpkg.com/@univerjs-pro/sheets-print/lib/index.css">

        <script src="https://unpkg.com/@univerjs-pro/sheets-exchange-client/lib/umd/index.js"></script>
        <link rel="stylesheet" href="https://unpkg.com/@univerjs-pro/sheets-exchange-client/lib/index.css">
        <style>
          body {
            margin: 0;
            padding: 0;
            font-family: Arial, sans-serif;
          }

          #app {
            height: 100vh;
            width: 100vw;
          }
        </style>
      </head>

      <body>
        <div id="app"></div>

        <script>
          // Hi, developer, this is a simple example to show how to use Univer UMD with collaboration, live share, print, exchange
          // If you want to use the collaboration, live share, print, exchange, you need to config the endpoint
          // The endpoint is the univer backend server that provides the collaboration, live share, print, exchange service
          // You can deploy the universer server on your own server, see the deployment guide: https://univer.ai/zh-CN/pro/guides/sheet/deployment/docker

          const universerEndpoint = 'localhost:8000';

          // check if the unit is already created
          const url = new URL(window.location.href)
          const unit = url.searchParams.get('unit')
          if (unit) {
            Promise.all([
              fetch('https://unpkg.com/@univerjs-pro/collaboration-client/lib/locale/en-US.json').then(res => res.json()),
              fetch('https://unpkg.com/@univerjs-pro/sheets-print/lib/locale/en-US.json').then(res => res.json()),
              fetch('https://unpkg.com/@univerjs-pro/sheets-exchange-client/lib/locale/en-US.json').then(res => res.json())
            ]).then(([
              collaborationLocale,
              printLocale,
              exchangeLocale
            ]) => {
              setup({
                ...collaborationLocale,
                ...printLocale,
                ...exchangeLocale
              });
            })
          } else {
            const { UniverInstanceType } = window.UniverCore;
            fetch(`http://${universerEndpoint}/universer-api/snapshot/${UniverInstanceType.UNIVER_SHEET}/unit/-/create`, {
              method: 'POST',
              headers: {
                'Content-Type': 'application/json',
              },
              body: JSON.stringify({
                type: UniverInstanceType.UNIVER_SHEET,
                name: 'New Sheet By Univer',
                creator: 'user',
              }),
            }).then((response) => {
              if (!response.ok) {
                throw new Error('Failed to create new sheet')
              }

              return response.json()
            }).then((data) => {
              if (!data.unitID) {
                throw new Error('create unit failed')
              }

              url.searchParams.set('unit', data.unitID)
              url.searchParams.set('type', String(UniverInstanceType.UNIVER_SHEET))
              window.location.href = url.toString()
            }).catch((error) => {
              console.error(error)
            })
          }

          const setup = (extLocale) => {
            var {
              UniverCore,
              UniverDesign,
              UniverEngineRender,
              UniverEngineFormula,
              UniverDocs,
              UniverDocsUi,
              UniverUi,
              UniverSheets,
              UniverSheetsUi,
              UniverSheetsNumfmt,
              UniverCollaboration,
              UniverCollaborationClient,
              UniverSheetsThreadComment
            } = window

            var univer = new UniverCore.Univer({
              theme: UniverDesign.defaultTheme,
              locale: UniverCore.LocaleType.EN_US,
              locales: {
                [UniverCore.LocaleType.EN_US]: {
                  ...UniverUMD['en-US'],
                  ...extLocale
                },
              },
              override: [
                [UniverCore.IAuthzIoService, null],
                [UniverCore.IUndoRedoService, null]
              ]
            });

            univer.registerPlugin(UniverEngineRender.UniverRenderEnginePlugin);
            univer.registerPlugin(UniverEngineFormula.UniverFormulaEnginePlugin);

            univer.registerPlugin(UniverUi.UniverUIPlugin, {
              container: "app",
            });

            univer.registerPlugin(UniverDocs.UniverDocsPlugin, {
              hasScroll: false,
            });
            univer.registerPlugin(UniverDocsUi.UniverDocsUIPlugin);

            univer.registerPlugin(UniverSheets.UniverSheetsPlugin);
            univer.registerPlugin(UniverSheetsUi.UniverSheetsUIPlugin);

            const { IThreadCommentMentionDataService, UniverSheetsThreadCommentPlugin } = UniverSheetsThreadComment;
            const mockUser = {
              userID: 'mockId',
              name: 'MockUser',
              avatar: '',
              anonymous: false,
              canBindAnonymous: false,
            };
            class CustomMentionDataService {
              trigger = '@';

              async getMentions (search) {
                return [
                  {
                    id: mockUser.userID,
                    label: mockUser.name,
                    type: 'user',
                    icon: mockUser.avatar,
                  },
                  {
                    id: '2',
                    label: 'User2',
                    type: 'user',
                    icon: mockUser.avatar,
                  },
                ];
              }
            }

            univer.registerPlugin(UniverSheetsThreadCommentPlugin, {
              overrides: [[IThreadCommentMentionDataService, { useClass: CustomMentionDataService }]],
            });

            //   pro
            const injector = univer.__getInjector();
            const configService = injector.get(UniverCore.IConfigService);

            // debug via reverse proxy
            const { SNAPSHOT_SERVER_URL_KEY, COLLAB_SUBMIT_CHANGESET_URL_KEY, COLLAB_WEB_SOCKET_URL_KEY, AUTHZ_URL_KEY } = UniverCollaborationClient;

            // config collaboration endpoint
            configService.setConfig(AUTHZ_URL_KEY, `http://${universerEndpoint}/universer-api/authz`);
            configService.setConfig(SNAPSHOT_SERVER_URL_KEY, `http://${universerEndpoint}/universer-api/snapshot`);
            configService.setConfig(COLLAB_SUBMIT_CHANGESET_URL_KEY, `http://${universerEndpoint}/universer-api/comb`);
            configService.setConfig(COLLAB_WEB_SOCKET_URL_KEY, `ws://${universerEndpoint}/universer-api/comb/connect`);

            // collaboration
            univer.registerPlugin(UniverCollaboration.UniverCollaborationPlugin);
            univer.registerPlugin(UniverCollaborationClient.UniverCollaborationClientPlugin);

            // live share
            univer.registerPlugin(UniverLiveShare.UniverLiveSharePlugin)

            // print
            univer.registerPlugin(UniverSheetsPrint.UniverSheetsPrintPlugin)

            // config import & export endpoint
            const { EXCHANGE_UPLOAD_FILE_SERVER_URL_KEY, EXCHANGE_IMPORT_SERVER_URL_KEY, EXCHANGE_EXPORT_SERVER_URL_KEY, EXCHANGE_GET_TASK_SERVER_URL_KEY, EXCHANGE_SIGN_URL_SERVER_URL_KEY } = UniverSheetsExchangeClient;
            configService.setConfig(EXCHANGE_UPLOAD_FILE_SERVER_URL_KEY, `http://${universerEndpoint}/universer-api/stream/file/upload`);
            configService.setConfig(EXCHANGE_IMPORT_SERVER_URL_KEY, `http://${universerEndpoint}/universer-api/exchange/{type}/import`);
            configService.setConfig(EXCHANGE_EXPORT_SERVER_URL_KEY, `http://${universerEndpoint}/universer-api/exchange/{type}/export`);
            configService.setConfig(EXCHANGE_GET_TASK_SERVER_URL_KEY, `http://${universerEndpoint}/universer-api/exchange/task/{taskID}`);
            configService.setConfig(EXCHANGE_SIGN_URL_SERVER_URL_KEY, `http://${universerEndpoint}/universer-api/file/{fileID}/sign-url`);

            // import & export
            univer.registerPlugin(UniverSheetsExchangeClient.UniverSheetsExchangeClientPlugin)
          }
        </script>
      </body>
      </html>
      ```
    </Tabs.Tab>
  </Tabs>
</Steps>

## Next Steps

Congratulations on making it this far! You're well on your way to mastering Univer. Here are some next steps to help you continue your journey:

- **🔰 Installation & Usage**: If you want to learn how to manually set up a Univer project from scratch, check out the [Installation & Usage](/guides/sheet/getting-started/installation) chapter. It will guide you through the process step by step.
- **🏗️ Advanced Usage**: Ready to take your Univer skills to the next level? The [Advanced Usage](/guides/sheet/advanced/custom-canvas) chapter covers more advanced topics and techniques for working with Univer.
- **📚 Tutorials**: Looking for practical examples and real-world use cases? Head over to the [Tutorials](/guides/sheet/tutorials/csv-import-plugin) chapter, where you'll find a collection of hands-on tutorials that demonstrate how to build various applications and features with Univer.
- **🧱 Concepts & Architecture**: Want to dive deep into the inner workings of Univer? The [Architecture](/guides/sheet/architecture/univer) chapter provides a comprehensive overview of Univer's architecture, core concepts, and design principles.
- **🎢 Playground**: Don't forget to explore the [Playground page](/playground), where you can experiment with various Univer demos and see the library in action.

No matter which path you choose, Univer is here to support you every step of the way. Happy coding!
